package cn.csc.module.product.dal.mysql.extension;

import cn.csc.framework.common.pojo.PageResult;
import cn.csc.framework.mybatis.core.mapper.BaseMapperX;
import cn.csc.framework.mybatis.core.query.LambdaQueryWrapperX;
import cn.csc.framework.mybatis.core.query.LambdaUpdateWrapperX;
import cn.csc.module.product.controller.admin.extension.vo.SpuExtensionExportReqVO;
import cn.csc.module.product.controller.admin.extension.vo.SpuExtensionPageReqVO;
import cn.csc.module.product.dal.dataobject.extension.SpuExtensionDO;
import cn.csc.module.product.dal.dataobject.stocklock.SkuStockLockDO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;

import java.math.BigInteger;
import java.util.List;

/**
 * 商品扩展信息 Mapper
 *
 * @author liuchuang
 */
@Mapper
public interface SpuExtensionMapper extends BaseMapperX<SpuExtensionDO> {

    default PageResult<SpuExtensionDO> selectPage(SpuExtensionPageReqVO reqVO) {
        return selectPage(reqVO, new LambdaQueryWrapperX<SpuExtensionDO>()
                .eqIfPresent(SpuExtensionDO::getSpuId, reqVO.getSpuId())
                .eqIfPresent(SpuExtensionDO::getSaleNum, reqVO.getSaleNum())
                .eqIfPresent(SpuExtensionDO::getActualStock, reqVO.getActualStock())
                .eqIfPresent(SpuExtensionDO::getLockStock, reqVO.getLockStock())
                .eqIfPresent(SpuExtensionDO::getStock, reqVO.getStock())
                .betweenIfPresent(SpuExtensionDO::getCreateTime, reqVO.getCreateTime())
                .orderByDesc(SpuExtensionDO::getId));
    }

    default List<SpuExtensionDO> selectList(SpuExtensionExportReqVO reqVO) {
        return selectList(new LambdaQueryWrapperX<SpuExtensionDO>()
                .eqIfPresent(SpuExtensionDO::getSpuId, reqVO.getSpuId())
                .eqIfPresent(SpuExtensionDO::getSaleNum, reqVO.getSaleNum())
                .eqIfPresent(SpuExtensionDO::getActualStock, reqVO.getActualStock())
                .eqIfPresent(SpuExtensionDO::getLockStock, reqVO.getLockStock())
                .eqIfPresent(SpuExtensionDO::getStock, reqVO.getStock())
                .betweenIfPresent(SpuExtensionDO::getCreateTime, reqVO.getCreateTime())
                .orderByDesc(SpuExtensionDO::getId));
    }

    /**
     * 通过订单减少库存
     *
     * @param spuId 商品id
     * @param count 数量
     * @return
     */
    default int reduceStockByOrder(@Param("spuId") BigInteger spuId, @Param("count") Integer count){
        LambdaUpdateWrapperX<SpuExtensionDO> updateWrapper = new LambdaUpdateWrapperX();
        updateWrapper.decreField(SpuExtensionDO::getStock,count);
        updateWrapper.increField(SpuExtensionDO::getLockStock,count);
        updateWrapper.eq(SpuExtensionDO::getSpuId,spuId);
        updateWrapper.ge(SpuExtensionDO::getStock,count);
        return update(null,updateWrapper);
    }

    /**
     * 通过减少库存
     *
     * @param spuId 商品id
     * @param count 数量
     * @return
     */
    default int reduceStockByOrderNotify(@Param("spuId") BigInteger spuId, @Param("count") Integer count){
        LambdaUpdateWrapperX<SpuExtensionDO> updateWrapper = new LambdaUpdateWrapperX();
        updateWrapper.decreField(SpuExtensionDO::getStock,count);
        updateWrapper.decreField(SpuExtensionDO::getActualStock,count);
        updateWrapper.increField(SpuExtensionDO::getSaleNum,count);
        updateWrapper.eq(SpuExtensionDO::getSpuId,spuId);
        return update(null,updateWrapper);
    }

    /**
     * 改替库存
     *
     * @param spuId 商品id
     * @param count 数量
     * @return
     */
    default int replaceStock(@Param("spuId") BigInteger spuId, @Param("count") Integer count){
        LambdaUpdateWrapperX<SpuExtensionDO> updateWrapper = new LambdaUpdateWrapperX();
        updateWrapper.set(SpuExtensionDO::getStock,count);
        updateWrapper.set(SpuExtensionDO::getActualStock,count);
        updateWrapper.eq(SpuExtensionDO::getSpuId,spuId);
        return update(null,updateWrapper);
    }

    Integer addStockByOrder(@Param("skuWithStocks") List<SkuStockLockDO> skuWithStocks);

    /**
     * 通过订单减少实际库存
     *
     * @param skuWithStocks 库存信息
     */
    Integer reduceActualStockByOrder(@Param("skuWithStocks") List<SkuStockLockDO> skuWithStocks);

    /**
     * 通过已经取消的订单减少实际库存
     *
     * @param skuWithStocks 库存信息
     */
    Integer reduceActualStockByCancelOrder(@Param("skuWithStocks") List<SkuStockLockDO> skuWithStocks);



}
